'''
Created on 17 jan 2010

@author: rlindeman

The question answering system
'''

import time

import rai.sem.FOL
import rai.tagger.sentencereader
import rai.sem.prover
import rai.logger.logger as logger
import rai.sem.grammarutil

class QASystem:
    
    def __init__(self, facts_location=None, grammar_location=None,trace=0):
        """
            @param grammar_location: location of the grammar file, with 'file:' prefix 
        """
        self.facts_location = facts_location
        self.grammar_location = grammar_location
        self.world = rai.sem.FOL.World(grammar_file=grammar_location)
        self.grammarUtil = rai.sem.grammarutil.GrammarUtil(grammar_location=self.grammar_location,trace=trace)
        
        self.logic_expressions = []
        self.timing = {}
        self.prover = rai.sem.prover.ProverWrapper()

        
    def setTrace(self, trace):
        self.trace = trace
        self.grammarUtil.trace = trace

    def parseFacts(self, facts_location=None, max=-1):
        if (facts_location is not None):
            self.facts_location = facts_location
        
        facts = [] # list of sentences that were analyzed and added to the grammar rules
        exceptions = []
        
        logger.LOG_ON = False
        reader = rai.tagger.sentencereader.SentenceReader()
        
        t0 = time.clock() # start tagger/chunker component timing
        parsedSentences = reader.parseFile(filename=self.facts_location, maxlines=max,collapse_PP=False)
        t1 = time.clock()# end start tagger/chunker component timing

        parser = rai.tagger.sentenceparser.SentenceParser()
        totalTimeAddFacts = 0
        totalTimeGrammar = 0
        t2 = time.clock()
        for parsed_sentence in parsedSentences:
            t0_fact = time.clock()
            info = self.world.addFact(parsed_sentence)
            t1_fact = time.clock()
            #print info
            line = parser.getSentence(parsed_sentence)
            t0_grammar = time.clock()
            if self.grammarUtil.isSentCovered(line):
                facts.append(line)
                logic_expression = self.grammarUtil.convertSentToExpr(line)
                self.logic_expressions.append(logic_expression)
            t1_grammar = time.clock()
            # total timing   
            totalTimeAddFacts = totalTimeAddFacts + (t1_fact - t0_fact)
            totalTimeGrammar = totalTimeGrammar + (t1_grammar - t0_grammar)
        t3 = time.clock()
        timeChunker = t1 - t0
        timeGrammar = t3 - t2
        
        avgAddFact = totalTimeAddFacts / len(parsedSentences)
        self.timing["grammar_addfact"] = totalTimeAddFacts
        self.timing["grammar_parse"] = totalTimeGrammar
        self.timing["chunker"] = timeChunker      
        self.timing["grammar"] = timeGrammar
    
    def question(self, question):
        self.question = question
        if not self.grammarUtil.isSentCovered(self.question):
            raise Exception("Question could not be parsed by the grammar")

    
    def answer(self, verbose=False):
        self.prover.add_expression_assumptions(self.logic_expressions)

        goal = self.grammarUtil.convertSentToExpr(self.question)
        self.prover.set_expression_goal(goal)
        t0 = time.clock()
        proofFound = self.prover.prove(verbose)
        t1 = time.clock()
        timeProver = t1 - t0
        self.timing["prover"] = timeProver
        return proofFound      